package xyz.strasae.androidlearn.regiongrow;

import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.appcompat.app.AppCompatActivity;
import androidx.core.app.ActivityCompat;

import android.Manifest;
import android.app.Activity;
import android.app.AlertDialog;
import android.content.DialogInterface;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.net.Uri;
import android.os.Build;
import android.os.Bundle;
import android.os.Handler;
import android.os.Looper;
import android.os.Message;
import android.text.TextUtils;
import android.util.Log;
import android.view.Menu;
import android.view.MenuItem;
import android.view.Window;
import android.widget.EditText;
import android.widget.ImageView;
import android.widget.TextView;
import android.widget.Toast;

import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.lang.reflect.Method;
import java.net.Socket;
import java.util.Arrays;

import xyz.strasae.androidlearn.regiongrow.task.GetImageCodeTask;
import xyz.strasae.androidlearn.regiongrow.task.UploadHttpTask;
import xyz.strasae.androidlearn.regiongrow.thread.ClientThread;
import xyz.strasae.androidlearn.regiongrow.utils.RealPathFromUriUtils;

public class MainActivity extends AppCompatActivity implements UploadHttpTask.OnUploadHttpListener, GetImageCodeTask.OnImageCodeListener {
    private String[] mPermissionList = {Manifest.permission.WRITE_EXTERNAL_STORAGE, Manifest.permission.READ_EXTERNAL_STORAGE};
    private ImageView iv_origin_image;
    private ImageView iv_image;
    private static final int REQUEST_PICK_IMAGE = 11101;
    private EditText et_http_url;
    private boolean bRunning = false;
    private Socket socket;
    private OutputStream out;
    private InputStream in;
    private byte[] GFileName = new byte[1024];
    private String sodd = ClientThread.SOCKET_IP;
    private String GName;
    private String fileName;
    private static final int IMAGE = 1;
    private String uploadFileName;
    private int cnt = 1;
    private ImageView iv_seed_image;
    private ImageView iv_current_image;
    private TextView tv_round;
    private TextView tv_MDL;
    private TextView tv_region;
    private int VALUE = 2;
    private String receiveHash = "Not Received";
    private static final int HASH = 3;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        iv_origin_image = findViewById(R.id.iv_origin_image);
        iv_image = findViewById(R.id.iv_image);
        iv_seed_image = findViewById(R.id.iv_seed_image);
        iv_current_image = findViewById(R.id.iv_current_image);
        tv_round = findViewById(R.id.tv_round);
        tv_region = findViewById(R.id.tv_region);
        tv_MDL = findViewById(R.id.tv_MDL);
        et_http_url = findViewById(R.id.et_http_url);
        et_http_url.setText(ClientThread.REQUEST_URL + "/uploadServlet");
        new Thread(new Runnable() {
            @Override
            public void run() {
                try {
                    socket = new Socket(sodd,9999); // 建立socket连接
                    in = socket.getInputStream();	// 初始化输入流对象
                    out = socket.getOutputStream();	// 初始化输出流对象
                } catch (IOException e) {
                    e.printStackTrace();
                }
                while(true){  //保持监听请求
                    try {
                        if(in == null) {
                            in = socket.getInputStream();
                        }
                        in.read(GFileName);  //读取图片 
                        GName = new String(GFileName);
                        fileName = GName;
                        if(fileName.indexOf('v') == 0) {  
                            UIHandler.sendEmptyMessage(VALUE);
                        } else if(fileName.indexOf('h') == 0) {
                            UIHandler.sendEmptyMessage(HASH);
                        }
                        else {
                            UIHandler.sendEmptyMessage(IMAGE);
                        }
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
            }
        }).start();
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        this.getMenuInflater().inflate(R.menu.menu_app, menu);
        setOverflowIconVisible(8, menu);
        return super.onCreateOptionsMenu(menu);
    }

    @Override
    public boolean onOptionsItemSelected(@NonNull MenuItem item) {
        int id = item.getItemId();
        if(id == R.id.menu_upload_image) {
            ActivityCompat.requestPermissions(MainActivity.this, mPermissionList, 100);
        } else if(id == R.id.menu_hash) {
            AlertDialog.Builder builder = new AlertDialog.Builder(MainActivity.this);
            builder.setTitle("Generated Block");
            builder.setMessage(receiveHash);
            builder.setPositiveButton("OK", new DialogInterface.OnClickListener() {
                @Override
                public void onClick(DialogInterface dialogInterface, int i) {

                }
            });
            AlertDialog alertDialog = builder.create();
            alertDialog.show();
        }
        return super.onOptionsItemSelected(item);
    }

    public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
        super.onRequestPermissionsResult(requestCode, permissions, grantResults);
        switch (requestCode) {
            case 100:
                boolean writeExternalStorage = grantResults[0] == PackageManager.PERMISSION_GRANTED;
                boolean readExternalStorage = grantResults[1] == PackageManager.PERMISSION_GRANTED;
                Log.e("MainActivity", Arrays.toString(grantResults));
                if (grantResults.length > 0 && writeExternalStorage && readExternalStorage) {
                    getImage();
                } else {
                    Toast.makeText(this, "请设置必要权限", Toast.LENGTH_SHORT).show();
                }
                break;
        }
    }

    private void getImage() {
        if(Build.VERSION.SDK_INT < Build.VERSION_CODES.KITKAT) {
            startActivityForResult(new Intent(Intent.ACTION_GET_CONTENT).setType("image/*"), REQUEST_PICK_IMAGE);
        } else {
            Intent intent = new Intent(Intent.ACTION_OPEN_DOCUMENT);
            intent.addCategory(Intent.CATEGORY_OPENABLE);
            intent.setType("image/*");
            startActivityForResult(intent, REQUEST_PICK_IMAGE);
        }
    }

    @Override
    protected void onActivityResult(int requestCode, int resultCode, @Nullable Intent data) {
        super.onActivityResult(requestCode, resultCode, data);
        if(resultCode == Activity.RESULT_OK) {
            switch(requestCode) {
                case REQUEST_PICK_IMAGE:
                    if(null != data) {
                        String realPathFromUri = RealPathFromUriUtils.getRealPathFromUri(this, data.getData());
                        uploadFileName = realPathFromUri.substring(realPathFromUri.lastIndexOf("/") + 1);
                        Bitmap bitmap = BitmapFactory.decodeFile(realPathFromUri);
                        iv_origin_image.setImageBitmap(bitmap);
                        String http_url = et_http_url.getText().toString();
                        if(TextUtils.isEmpty(http_url)) {
                            Toast.makeText(this, "上传地址错误！", Toast.LENGTH_SHORT).show();
                        } else {
                            UploadHttpTask uploadHttpTask = new UploadHttpTask(this);
                            uploadHttpTask.setOnUploadHttpListener(this);
                            uploadHttpTask.execute(new String[] {http_url, realPathFromUri});
                        }
                    } else {
                        Toast.makeText(this, "图片损坏，请重新选择", Toast.LENGTH_SHORT).show();
                    }
            }
        }
    }

    @Override
    public void onUploadFinish(final String result) {
        if(result.equals("SUCCESSFUL")) {
            Toast.makeText(this, "Upload Finish", Toast.LENGTH_SHORT).show();
        } else {
            Toast.makeText(this, "Upload Failed", Toast.LENGTH_SHORT).show();
        }
        final byte[] sFileName = uploadFileName.getBytes();
        new Thread(new Runnable() {
            @Override
            public void run() {
                try {
                    out.write(sFileName);
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }).start();
    }

    @Override
    public void onGetCode(String path) {
        Uri uri = Uri.parse(path);
        if(cnt == 1) {
            iv_seed_image.setImageURI(uri);
        }
        else if(cnt == 2) {
            iv_image.setImageURI(uri);
        } else {
            iv_current_image.setImageURI(uri);
        }
        cnt++;
        bRunning = false;
    }

    private void getImageCode(String fileName) {
        if(bRunning != true) {
            bRunning = true;
            GetImageCodeTask codeTask = new GetImageCodeTask(this, ClientThread.REQUEST_URL + "/" + fileName);
            codeTask.setOnImageCodeListener(this);
            codeTask.execute();
        }
    }

    private Handler UIHandler = new Handler() {
        @Override
        public void handleMessage(@NonNull Message msg) {
            if(msg.what == IMAGE) {
                if(cnt <= 2)
                    getImageCode(fileName);
                else
                    getImageCode("pre_best.bmp");
            } else if(msg.what == VALUE) {
                String[] value = fileName.split(" ");
                tv_round.setText(String.format("Round:%s", value[1]));
                tv_region.setText(String.format("Region A:%s  Region B:%s", value[2], value[3]));
                tv_MDL.setText(String.format("MDL:%s", value[4]));
            } else if(msg.what == HASH) {
                receiveHash = fileName.substring(fileName.indexOf('h') + 1);
            }
        }
    };

    private void setOverflowIconVisible(int featureId, Menu menu) {
        //actionbar的featureId是8 ToolBar的是108
        if(featureId % 100 == Window.FEATURE_ACTION_BAR && menu != null) {
            if(menu.getClass().getSimpleName().equals("MenuBuilder")) {
                try {
                    Method method = menu.getClass().getDeclaredMethod("setOptionalIconsVisible", Boolean.TYPE);
                    method.setAccessible(true);
                    method.invoke(menu, true);
                } catch(Exception e) {
                }
            }
        }
    }
}
